package cn.juque.systemservice.service.impl;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.map.MapUtil;
import cn.hutool.core.text.CharSequenceUtil;
import cn.hutool.core.util.StrUtil;
import cn.juque.common.constants.MessageEnum;
import cn.juque.common.constants.NumberConstant;
import cn.juque.common.constants.StringConstants;
import cn.juque.common.exception.AppException;
import cn.juque.systemservice.bo.AreaInfoBO;
import cn.juque.systemservice.cache.AreaInfoCache;
import cn.juque.systemservice.entity.AreaInfo;
import cn.juque.systemservice.mapper.AreaInfoMapper;
import cn.juque.systemservice.service.IAreaInfoService;
import com.baomidou.mybatisplus.extension.toolkit.SqlHelper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

/**
 * @author JUQUE
 * @version 1.0.0
 * <ul>
 *  <li>simple-generator</li>
 *  <li>地区信息</li>
 * </ul>
 * @date 2022-10-27 21:15:33
 **/
@Slf4j
@Service("areaInfoService")
public class AreaInfoServiceImpl implements IAreaInfoService {

    @Resource
    private AreaInfoMapper areaInfoMapper;

    @Resource
    private AreaInfoCache areaInfoCache;

    /**
     * 查询
     *
     * @param areaInfo areaInfo
     * @return List
     */
    @Override
    public List<AreaInfo> listInfoWithoutPage(AreaInfo areaInfo) {
        return this.areaInfoMapper.queryInfoList(areaInfo);
    }

    /**
     * 根据编码查询
     *
     * @param codeList 编码
     * @return list
     */
    @Override
    public List<AreaInfoBO> listByCode(List<String> codeList) {
        if (CollUtil.isEmpty(codeList)) {
            return CollUtil.newArrayList();
        }
        return codeList.stream().map(t -> this.areaInfoCache.node(t)).collect(Collectors.toList());
    }

    /**
     * 详情
     *
     * @param id 主键
     * @return AreaInfo
     */
    @Override
    public AreaInfoBO detail(String id) {
        AreaInfo areaInfo = this.areaInfoMapper.selectById(id);
        return this.areaInfoCache.node(areaInfo.getAreaCode());
    }

    /**
     * 保存
     *
     * @param areaInfo areaInfo
     */
    @Override
    public void saveInfo(AreaInfo areaInfo) {
        // 校验id是否重复.
        if (null != this.selectByCode(areaInfo.getAreaCode())) {
            throw new AppException("保存失败,对象ID【" + areaInfo.getAreaCode() + "】已经存在!");
        }
        boolean flag = SqlHelper.retBool(this.areaInfoMapper.insert(areaInfo));
        if (!flag) {
            throw new AppException(MessageEnum.SAVE_FAIL);
        }
        // 刷新缓存
        this.areaInfoCache.refreshTree();
    }

    /**
     * 更新
     *
     * @param areaInfo areaInfo
     */
    @Override
    public void updateInfo(AreaInfo areaInfo) {
        boolean flag = SqlHelper.retBool(this.areaInfoMapper.updateById(areaInfo));
        if (!flag) {
            throw new AppException(MessageEnum.UPDATE_FAIL);
        }
        // 刷新缓存
        this.areaInfoCache.refreshTree();
    }

    /**
     * 删除
     *
     * @param ids 主键列表
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public void deleteInfo(List<String> ids) {
        if (CollUtil.isEmpty(ids)) {
            return;
        }
        ids.forEach(t -> {
            AreaInfo areaInfo = new AreaInfo();
            areaInfo.setId(t);
            areaInfo.setIsDelete(NumberConstant.ONE);
        });
        // 刷新缓存
        this.areaInfoCache.refreshTree();
    }

    /**
     * 同步地区信息
     *
     * @param content html
     */
    @Override
    public void loadAreaInfo(String content) {
        Map<String, AreaInfo> map = MapUtil.newHashMap();
        AreaInfo china = new AreaInfo();
        china.setAreaCode("CHN");
        china.setAreaName("中国");
        map.put("中国", china);
        content = CharSequenceUtil.replace(content, "<td class=\"xl1516790\"></td>", "");
        List<String> contentList = CharSequenceUtil.split(content, "</tr>");
        for (String t : contentList) {
            String code = CharSequenceUtil.subBefore(t, "</td>", false);
            code = CharSequenceUtil.subAfter(code, ">", true);
            String nameTd = StrUtil.subAfter(t, "<td", true);
            nameTd = CharSequenceUtil.subAfter(nameTd, ">", false);
            String nameStr = StrUtil.subBefore(nameTd, "<", true);
            nameStr = CharSequenceUtil.replace(nameStr, ",,", ",");
            if (CharSequenceUtil.isBlank(nameStr)) {
                log.info(">>>>code=" + code + "nameStr=" + nameStr);
                continue;
            }
            List<String> nameList = StrUtil.split(nameStr, StringConstants.COMMA);
            for (int i = 0; i < nameList.size(); i++) {
                if (map.containsKey(nameList.get(i))) {
                    continue;
                }
                if (i == 0) {
                    System.out.println(">>>>" + nameStr);
                }
                AreaInfo parentArea = map.get(nameList.get(i - 1));
                AreaInfo areaInfo = new AreaInfo();
                areaInfo.setAreaName(nameList.get(i));
                areaInfo.setParentAreaCode(parentArea.getAreaCode());
                areaInfo.setAreaCode(code);
                areaInfo.setCreateUserId("1");
                areaInfo.setCreateOrgId("hosa");
                areaInfo.setUpdateUserId("1");
                areaInfo.setUpdateOrgId("fj");
                this.areaInfoMapper.insert(areaInfo);
                map.put(nameList.get(i), areaInfo);
            }
        }
    }

    /**
     * 地区编码查询
     *
     * @param areaCode 地区编码
     * @return AreaInfo
     */
    private AreaInfo selectByCode(String areaCode) {
        AreaInfo areaInfo = new AreaInfo();
        areaInfo.setAreaCode(areaCode);
        List<AreaInfo> list = this.areaInfoMapper.queryInfoList(areaInfo);
        return CollUtil.isEmpty(list) ? null : list.get(0);
    }
}
